#include "key_board/key_board_sample.h"

static TimerHandle_t tmr_handle;
static void TimerCallbackFun( TimerHandle_t xTimer );

static unsigned int test_id1, test_id2;

/*app task creat*/
void AppTaskCreat(void)
{
    tmr_handle = xTimerCreate((const char *) "tmr1",
                              (TickType_t) 10,
                              (UBaseType_t) pdTRUE,
                              (void *) 1,
                              (TimerCallbackFunction_t) TimerCallbackFun );

    GPIO_Key_Board_Init();

    struct key_combine_t test_combine1[] = {
        {
            .id = KEY_UP,
            .state = KEY_PRESS
        },
        {
            .id = KEY_DOWN,
            .state = KEY_PRESS_LONG
        },
        {
            .id = KEY_UP,
            .state = KEY_PRESS
        },
    };
    test_id1 = key_combine_register(test_combine1, ARRAY_SIZE(test_combine1));

    struct key_combine_t test_combine2[] = {
        {
            .id = KEY_UP,
            .state = KEY_PRESS
        },
        {
            .id = KEY_DOWN,
            .state = KEY_PRESS
        },
        {
            .id = KEY_UP,
            .state = KEY_PRESS
        },
        {
            .id = KEY_DOWN,
            .state = KEY_PRESS
        },
    };
    test_id2 = key_combine_register(test_combine2, ARRAY_SIZE(test_combine2));

    if(tmr_handle != NULL)
    {
        xTimerStart(tmr_handle, 0);
    }
}

/*tmr1 callback function*/
static void TimerCallbackFun( TimerHandle_t xTimer )
{
    (void)xTimer;
    unsigned int res;

    (void)res;

    //扫描按键（10ms一次）
    key_check();

    //实际上下面的检测可以在代码的任意地方，我这里只是为了方便测试
    //因为我这里按键扫描周期是10ms，也就是10ms才会更新一次按键的状态，
    //当在一个循环中发现按键会重复触发这可能是因为你的检测周期远小于扫描周期，
    //按键状态还未更新，你的检测又来了就会出现这种情况
    if(key_check_state(KEY_UP, KEY_RELEASE))
    {
        PRINTF("KEY_UP KEY_RELEASE\r\n");
    }
    if(key_check_state(KEY_UP, KEY_PRESS))
    {
        PRINTF("KEY_UP KEY_PRESS\r\n");
    }
    if(key_check_state(KEY_UP, KEY_PRESS_LONG))
    {
        PRINTF("KEY_UP KEY_PRESS_LONG\r\n");
    }
    if(key_check_state(KEY_UP, KEY_RELEASE_LONG))
    {
        PRINTF("KEY_UP KEY_RELEASE_LONG\r\n");
    }
    res = key_check_state(KEY_UP, KEY_PRESS_MULTI);
    if(res)
    {
        PRINTF("KEY_UP KEY_PRESS_MULTI:%d\r\n", res);
    }
    res = key_check_state(KEY_UP, KEY_RELEASE_MULTI);
    if(res)
    {
        PRINTF("KEY_UP KEY_RELEASE_MULTI:%d\r\n", res);
    }
    if(key_check_state(KEY_UP, KEY_PRESS_CONTINUOUS))
    {
        PRINTF("KEY_UP KEY_PRESS_CONTINUOUS\r\n");
    }

    if(key_check_state(KEY_DOWN, KEY_RELEASE))
    {
        PRINTF("KEY_DOWN KEY_RELEASE\r\n");
    }
    if(key_check_state(KEY_DOWN, KEY_PRESS))
    {
        PRINTF("KEY_DOWN KEY_PRESS\r\n");
    }
    if(key_check_state(KEY_DOWN, KEY_PRESS_LONG))
    {
        PRINTF("KEY_DOWN KEY_PRESS_LONG\r\n");
    }
    if(key_check_state(KEY_DOWN, KEY_RELEASE_LONG))
    {
        PRINTF("KEY_DOWN KEY_RELEASE_LONG\r\n");
    }
    res = key_check_state(KEY_DOWN, KEY_PRESS_MULTI);
    if(res)
    {
        PRINTF("KEY_DOWN KEY_PRESS_MULTI:%d\r\n", res);
    }
    res = key_check_state(KEY_DOWN, KEY_RELEASE_MULTI);
    if(res)
    {
        PRINTF("KEY_DOWN KEY_RELEASE_MULTI:%d\r\n", res);
    }

    if(key_check_state(KEY_LEFT, KEY_RELEASE))
    {
        PRINTF("KEY_LEFT KEY_RELEASE\r\n");
    }
    if(key_check_state(KEY_LEFT, KEY_PRESS))
    {
        PRINTF("KEY_LEFT KEY_PRESS\r\n");
    }

    if(key_check_state(KEY_RIGHT, KEY_RELEASE))
    {
        PRINTF("KEY_RIGHT KEY_RELEASE\r\n");
    }
    if(key_check_state(KEY_RIGHT, KEY_PRESS))
    {
        PRINTF("KEY_RIGHT KEY_PRESS\r\n");
    }

    if(key_check_state(KEY_ENTER, KEY_RELEASE))
    {
        PRINTF("KEY_ENTER KEY_RELEASE\r\n");
    }
    if(key_check_state(KEY_ENTER, KEY_PRESS))
    {
        PRINTF("KEY_ENTER KEY_PRESS\r\n");
    }

    if(key_check_state(KEY_EXIT, KEY_RELEASE))
    {
        PRINTF("KEY_EXIT KEY_RELEASE\r\n");
    }
    if(key_check_state(KEY_EXIT, KEY_PRESS))
    {
        PRINTF("KEY_EXIT KEY_PRESS\r\n");
    }

    if((key_check_state(KEY_UP, KEY_PRESSING)) && (key_check_state(KEY_DOWN, KEY_PRESS)))
    {
        PRINTF("KEY_UP KEY_PRESSING && KEY_DOWN KEY_PRESS\r\n");
    }

    //与上面的组合相比，上面的组合需要多种状态同时存在
    //而此种组合是每个状态之间是允许存在一定时间差的，而且是保证顺序的
    if(key_check_combine_state(test_id1))
    {
        PRINTF("combine test_id1\r\n");
    }

    if(key_check_combine_state(test_id2))
    {
        PRINTF("combine test_id2\r\n");
    }
}
